package lp.polimi.treefinder;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import lp.polimi.treefinder.utils.FilesUtils;

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;


import android.app.Activity;
import android.app.ListFragment;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.SimpleAdapter;

/**
 * Displays the list of the tagged leaves. Basically fetches the tags data from a XML file,
 * retrieve the related pictures from the external storage and put each tag in
 * a list entry. The user can access the leaf details pushing the entry, unless the leaf in untagged
 * (was stored to tag it afterwards). In this last case a default image is loaded and pushing the entry
 * starts the tagging procedure.
 */
public class MyTagsFragment extends ListFragment {

	private ArrayList<HashMap<String, String>> menuItems;
	private NodeList nl;

	private MyTagsFragmentListener mListener;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		fetchXml();
	}

	@Override
	public void onResume() {
		super.onResume();
		updateList();
	}

	private void updateList() {
		boolean tagListNotEmpty = fetchXml();
		if (tagListNotEmpty) {
			setListAdapter(new ListAdapter(getActivity(), menuItems, R.layout.list_row,
					new String[] { XMLHandler.KEY_NAME, XMLHandler.KEY_DATE, XMLHandler.KEY_ADDRESS,
				XMLHandler.KEY_CITY, XMLHandler.KEY_COUNTRY, XMLHandler.KEY_UNKNOWN_ID},
				new int[] {R.id.list_name, R.id.date_value, R.id.address_row_tv,
				R.id.city_row_tv, R.id.country_row_tv}, "ITCEDSCR.TTF"));
		} else
			getActivity().getActionBar().getTabAt(1).select();
	}

	@Override
	public void onAttach(Activity activity) {
		super.onAttach(activity);
		try {
			mListener = (MyTagsFragmentListener) activity;
		} catch (ClassCastException e) {
			throw new ClassCastException(activity+" must implement MyTagsFragmentListener");
		}
		fetchXml();
	}


	/**
	 * @return True if the tags list is not empty, false if it's empty or an exception occurs.
	 */
	private boolean fetchXml() {
		menuItems = new ArrayList<HashMap<String, String>>();

		try {

			Document doc = XMLHandler.getDomElement(getActivity(), "leaves.xml"); // getting DOM element
			nl = doc.getElementsByTagName(XMLHandler.KEY_LEAF);


			for (int i = 0; i < nl.getLength(); i++) {
				// creating new HashMap
				HashMap<String, String> map = new HashMap<String, String>();
				Element e = (Element) nl.item(i);
				// adding each child node to HashMap key => value
				map.put(XMLHandler.KEY_NAME, XMLHandler.getValue(e, XMLHandler.KEY_NAME));
				map.put(XMLHandler.KEY_DATE, XMLHandler.getValue(e, XMLHandler.KEY_DATE));
				String unknownId = XMLHandler.getValue(e, XMLHandler.KEY_UNKNOWN_ID);
				map.put(XMLHandler.KEY_UNKNOWN_ID, unknownId);
				String address = XMLHandler.getValue(e, XMLHandler.KEY_ADDRESS);
				if (address!=null)
					map.put(XMLHandler.KEY_ADDRESS, address);
				else
					map.put(XMLHandler.KEY_ADDRESS, getResources().getString(R.string.not_address));
				String city = XMLHandler.getValue(e, XMLHandler.KEY_CITY);
				if (city!=null)
					map.put(XMLHandler.KEY_CITY, city);
				else
					map.put(XMLHandler.KEY_CITY, getResources().getString(R.string.not_city));
				String country = XMLHandler.getValue(e, XMLHandler.KEY_COUNTRY);
				if (country!=null)
					map.put(XMLHandler.KEY_COUNTRY, country);
				else
					map.put(XMLHandler.KEY_COUNTRY, getResources().getString(R.string.not_country));

				// adding HashList to ArrayList
				menuItems.add(0, map);
			}

			if (menuItems.size()==0)
				return false;
			else
				return true;

		} catch (Exception e) {
			e.printStackTrace();
			return false;
		}
	}

	@Override
	public void onActivityCreated(Bundle savedInstanceState) {
		super.onActivityCreated(savedInstanceState);

		// selecting single ListView item
		ListView lv = getListView();
		// listening to single listitem click
		lv.setOnItemClickListener(new OnItemClickListener() {

			@Override
			public void onItemClick(AdapterView<?> parent, View view, int position, long id) {

				Map<String, String> clicked = menuItems.get(position);

				if (clicked.get(XMLHandler.KEY_UNKNOWN_ID)==null) {
					Intent in = new Intent(getActivity().getApplicationContext(), LeafInsightsActivity.class);
					in.putExtra(XMLHandler.KEY_NAME, clicked.get(XMLHandler.KEY_NAME));
					in.putExtra(XMLHandler.KEY_DATE, clicked.get(XMLHandler.KEY_DATE));
					in.putExtra(XMLHandler.KEY_ADDRESS, clicked.get(XMLHandler.KEY_ADDRESS));
					in.putExtra(XMLHandler.KEY_CITY, clicked.get(XMLHandler.KEY_CITY));
					in.putExtra(XMLHandler.KEY_COUNTRY, clicked.get(XMLHandler.KEY_COUNTRY));
					startActivity(in);
				} else {
					mListener.tagUnknownLeaf(clicked.get(XMLHandler.KEY_UNKNOWN_ID));
				}
			}
		});
	}

	private class ListAdapter extends SimpleAdapter {


		public ListAdapter(Context context, List<? extends Map<String, ?>> data, int resource, String[] from, int[] to, String font) {
			super(context, data, resource, from, to);
		}

		@Override
		public View getView(int position, View convertView, ViewGroup parent) {
			String unknownId = menuItems.get(position).get(XMLHandler.KEY_UNKNOWN_ID);
			View view = super.getView(position, convertView, parent);
			ImageView imageView = (ImageView) view.findViewById(R.id.list_image);
			if (unknownId==null) {
				imageView.setImageBitmap(FilesUtils.retrieveLeafBitmap(getActivity(), menuItems.get(position).get(XMLHandler.KEY_NAME), "png"));
			} else {
				imageView.setImageBitmap(FilesUtils.retrieveLeafBitmap(getActivity(), "unknown_leaf", "png"));	
			}

			return view;
		}
	}

	public interface MyTagsFragmentListener {
		public void tagUnknownLeaf(String unknownId);
	}
}
